<html>
<head><meta charset="utf-8"><title>Understanding Macro Hygiene handling through hooks · t-compiler/help · Zulip Chat Archive</title></head>
<h2>Stream: <a href="https://rust-lang.github.io/zulip_archive/stream/182449-t-compiler/help/index.html">t-compiler/help</a></h2>
<h3>Topic: <a href="https://rust-lang.github.io/zulip_archive/stream/182449-t-compiler/help/topic/Understanding.20Macro.20Hygiene.20handling.20through.20hooks.html">Understanding Macro Hygiene handling through hooks</a></h3>

<hr>

<base href="https://rust-lang.zulipchat.com">

<head><link href="https://rust-lang.github.io/zulip_archive/style.css" rel="stylesheet"></head>

<a name="244958832"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/182449-t-compiler/help/topic/Understanding%20Macro%20Hygiene%20handling%20through%20hooks/near/244958832" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> BaSh <a href="https://rust-lang.github.io/zulip_archive/stream/182449-t-compiler/help/topic/Understanding.20Macro.20Hygiene.20handling.20through.20hooks.html#244958832">(Jul 05 2021 at 17:20)</a>:</h4>
<p>Hello,<br>
I would like to perform source to source transformation in the macros. Is there a compiler hook to understand the macro contexts?  How does the <code>first_x</code> refer to <code>x=1</code>? Is it expanded like a closure?</p>
<p>Following example is from <a href="https://github.com/dtolnay/cargo-expand">https://github.com/dtolnay/cargo-expand</a> </p>
<div class="codehilite"><pre><span></span><code>For instance the following function returns 3 when compiled ordinarily by Rust but the expanded code compiles and returns 4.
fn f() -&gt; i32 {
    let x = 1;
    macro_rules! first_x {
        () =&gt; { x }
    }
    let x = 2;
    x + first_x!()
}
</code></pre></div>



<a name="244960101"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/182449-t-compiler/help/topic/Understanding%20Macro%20Hygiene%20handling%20through%20hooks/near/244960101" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> bjorn3 <a href="https://rust-lang.github.io/zulip_archive/stream/182449-t-compiler/help/topic/Understanding.20Macro.20Hygiene.20handling.20through.20hooks.html#244960101">(Jul 05 2021 at 17:39)</a>:</h4>
<p>When identifiers are referenced inside a macro, they are resolved relative to the macro definition, not the macro invocation. So in this case <code>first_x!()</code> expands to an <code>x</code> that is resolved at the definition of <code>first_x!</code>, which means that it resolves to the first <code>x</code>.</p>



<a name="244961310"></a>
<h4><a href="https://rust-lang.zulipchat.com#narrow/stream/182449-t-compiler/help/topic/Understanding%20Macro%20Hygiene%20handling%20through%20hooks/near/244961310" class="zl"><img src="https://rust-lang.github.io/zulip_archive/assets/img/zulip.svg" alt="view this post on Zulip" style="width:20px;height:20px;"></a> BaSh <a href="https://rust-lang.github.io/zulip_archive/stream/182449-t-compiler/help/topic/Understanding.20Macro.20Hygiene.20handling.20through.20hooks.html#244961310">(Jul 05 2021 at 17:57)</a>:</h4>
<p><span class="user-mention silent" data-user-id="133247">bjorn3</span> <a href="#narrow/stream/182449-t-compiler.2Fhelp/topic/Understanding.20Macro.20Hygiene.20handling.20through.20hooks/near/244960101">said</a>:</p>
<blockquote>
<p>When identifiers are referenced inside a macro, they are resolved relative to the macro definition, not the macro invocation. So in this case <code>first_x!()</code> expands to an <code>x</code> that is resolved at the definition of <code>first_x!</code>, which means that it resolves to the first <code>x</code>.</p>
</blockquote>
<p>Thank You! Is there a way to see this through compiler hooks?  I tried with compiler dumps <code>cargo rustc --  -Z unpretty=expanded,hygiene</code> but it was not very clear about the procedure.  </p>
<div class="codehilite"><pre><span></span><code>fn f /* 476#0 */() -&gt; i32 /* 563#0 */ {
    let x /* 1309#0 */ = 1;

    macro_rules! first_x /* 1310#0 */ { () =&gt; { x } }

    let x /* 1309#0 */ = 2;

    x /* 1309#0 */ + x /* 1309#23 */                                                  &lt;---------- Different x values.
}
</code></pre></div>



<hr><p>Last updated: Aug 07 2021 at 22:04 UTC</p>
</html>